package ph.com.gs3.chat.model.valueobject.application;


import org.json.JSONException;
import org.json.JSONObject;

public class APIResponse {

	public static final String TAG = APIResponse.class.getSimpleName();

	public static enum APIStatus {
		SUCCESS, ERROR
	}

	private APIStatus status;

	private String results;
	private String error;
	private String errorMessage;
	private String serverDate;

	public APIResponse(JSONObject rawResponse) throws APIInvalidResponseException {

		String currentKey = "status";	// first key

		try {
			String rawStatus = rawResponse.getString(currentKey);

			if ("SUCCESS".equals(rawStatus)) {
				status = APIStatus.SUCCESS;
			} else if ("ERROR".equals(rawStatus)) {
				status = APIStatus.ERROR;
			} else {
				throw new APIInvalidResponseException(
				        "Invalid status key, it must be SUCCESS or ERROR only.");
			}

			currentKey = "error";
			error = rawResponse.getString(currentKey) == "null" ? null : rawResponse
			        .getString(currentKey);

			currentKey = "error_message";
			errorMessage = rawResponse.getString(currentKey) == "null" ? null : rawResponse
			        .getString(currentKey);

			currentKey = "results";
			results = rawResponse.getString(currentKey) == "null" ? null : rawResponse
			        .getString(currentKey);

			currentKey = "server_date";
			if (rawResponse.has(currentKey)) {
				serverDate = rawResponse.getString(currentKey);
			}

		} catch (JSONException e) {

			if (rawResponse.has(currentKey)) {
				try {
					throw new APIInvalidResponseException(
					        "Response has incomplete keys, it must have a valid " + currentKey
					                + " key. Its value is found to be: "
					                + rawResponse.getString(currentKey), e);
				} catch (JSONException e1) {
					throw new APIInvalidResponseException(
					        "Response has incomplete keys, it must have an valid " + currentKey
					                + " key.", e1);
				}
			} else {
				throw new APIInvalidResponseException(
				        "Response has incomplete keys, it must have an existing " + currentKey
				                + " key.", e);
			}

		}

	}

	// ============================================================================
	// Exceptions

	public static final class APIServerErrorException extends Exception {

		private static final long serialVersionUID = -7304320222247244020L;

		public APIServerErrorException(String message) {
			super(message);
		}

	}

	public static final class APIInvalidResponseException extends Exception {

		private static final long serialVersionUID = -3474666959648063230L;

		private static final String DEFAULT_MESSAGE = "The server gave an invalid response.";

		private String rawResponseString;

		public APIInvalidResponseException() {
			super(DEFAULT_MESSAGE);
		}

		public APIInvalidResponseException(Exception e) {
			super(DEFAULT_MESSAGE, e);
		}

		public APIInvalidResponseException(String message) {
			super(message);
		}

		public APIInvalidResponseException(String message, Exception e) {
			super(message, e);
		}

		public String getRawResponseString() {
			return rawResponseString;
		}

		public void setRawResponseString(String rawResponseString) {
			this.rawResponseString = rawResponseString;
		}

	}

	// ============================================================================
	// Getters & Setters

	public APIStatus getStatus() {
		return status;
	}

	public boolean operationSuccessful() {
		return status == APIStatus.SUCCESS;
	}

	public String getResults() {
		return results;
	}

	public String getError() {
		return error;
	}

	public String getErrorMessage() {
		return errorMessage;
	}

	public String getServerDate() {
		return serverDate;
	}

}
